/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package Engine.Scene;

import Engine.Game.GameAdmin;
import java.io.IOException;
import javax.microedition.lcdui.Graphics;
import javax.microedition.lcdui.Image;
import javax.microedition.lcdui.game.TiledLayer;

/**
 * Creates a new Map using an existing Map-compliant class. The requirements are a 15x10 information matrix and 32x32 pixels tiles.
 * @author Gerardo GalÃ­ndez
 */
public class Map extends TiledLayer {

    //--------------------------------------------------------------------------
    //Map and tile constants----------------------------------------------------
    /**
     * Number of tiles horizontally
     */
    public static final int HORIZONTAL_TILES = 15;
    /**
     * Number of tiles vertically
     */
    public static final int VERTICAL_TILES = 10;
    /**
     * The size of the tile
     */
    public static final int TILE_SIZE = 32;
    /**
     * The total width of the map
     */
    public static final int MAP_WIDTH = HORIZONTAL_TILES * TILE_SIZE;
    /**
     * The total height of the map
     */
    public static final int MAP_HEIGHT = VERTICAL_TILES * TILE_SIZE;
    //Scene integer constants---------------------------------------------------
    /**
     * Integer index code representing the fishbowl map
     */
    public static final int FISHBOWL = 0;
    /**
     * Integer index code representing the outer fishbowl map
     */
    public static final int OUTER_FISHBOWL = 1;
    /**
     * Integer index code representing the distillery map
     */
    public static final int DISTILLERY = 2;
    /**
     * Integer index code representing the wolves upper left map
     */
    public static final int WOLVES_UPPER_LEFT = 31;
    /**
     * Integer index code representing the wolves upper right map
     */
    public static final int WOLVES_UPPER_RIGHT = 32;
    /**
     * Integer index code representing the wolves upper right map
     */
    public static final int WOLVES_UPPER_RIGHT_2 = 321;
    /**
     * Integer index code representing the wolves lower left map
     */
    public static final int WOLVES_LOWER_LEFT = 33;
    /**
     * Integer index code representing the wolves lower right map
     */
    public static final int WOLVES_LOWER_RIGHT = 34;
    /**
     * Integer index code representing the outsides map
     */
    public static final int OUTSIDES = 4;
    /**
     * Integer index code representing the outer distillery map
     */
    public static final int OUTER_DISTILLERY = 5;
    /**
     * Integer index code representing the trees zone 1 map
     */
    public static final int TREES_ZONE_1 = 40;
    /**
     * Integer index code representing the trees zone 2 map
     */
    public static final int TREES_ZONE_2 = 41;
    /**
     * Integer index code representing the trees zone 3 map
     */
    public static final int TREES_ZONE_3 = 42;
    /**
     * Integer index code representing the red thing town map
     */
    public static final int RED_THING_TOWN = 5;
    /**
     * Integer index code representing the altar of wisdom map
     */
    public static final int ALTAR_OF_WISDOM = 6;
    /**
     * Integer index code representing the CCI-Receiver map
     */
    public static final int CCI_RECEIVER = 7;
    /**
     * Integer index code representing the CCI-Receiver map
     */
    public static final int CCI_RECEIVER_2 = 71;
    /**
     * Integer index code representing the CCI-Computers map
     */
    public static final int CCI_COMPUTERS = 8;
    private int mapType;
    private GameAdmin gameAdmin;
    //Fishbowl data-------------------------------------------------------------
    private static int[][] fishbowlTransitable =
         {{ 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2},
          { 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2}};

    private static int[][] fishbowlBounds =
         {{ 3, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3},
          { 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5},
          { 6, 0, 0, 7, 6, 0, 0, 7, 0, 0, 6, 0, 0, 6, 5},
          { 4, 0, 0, 8, 0, 0, 0, 8, 0, 9, 9, 9, 9, 9,10},
          { 6, 0, 0, 0, 0, 0, 0, 6, 5, 0, 0, 0, 0, 0, 0},
          { 4, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0},
          { 4, 0, 0, 7, 0, 0, 0, 7, 5, 0, 0, 0, 0, 0, 0},
          { 6, 0, 0, 8, 6, 0, 0, 8, 6,11,11,11,11,11,12},
          { 4, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          {13, 0, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9,10}};
    //OuterFishbowl data--------------------------------------------------------
    private static int[][] outerFishbowlTransitable =
          {{ 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5},
           { 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4},
           { 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3},
           { 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6},
           { 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7},
           { 8, 8, 8, 8, 8, 9, 8, 8, 8, 8, 8, 8, 8, 9, 8},
           { 8, 9, 8, 8, 8, 8, 8, 8, 8, 9, 8, 8, 8, 8, 8},
           { 8, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 9},
           { 8, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 8}};
    
    private static int[][] outerFishBowlBounds =
          {{10, 0,10,10,10,10,10,10,10,10,10,10,10,10,10},
           { 0, 0, 0,11, 0, 0,11, 0, 0,11, 0, 0,11, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
           { 0, 0,12,13,13,13,13,13,13,13,13,13,14, 0, 0},
           {15,15,16,17,17,17,17,17,17,17,17,17,18,15,15}};
    //Distillery data-----------------------------------------------------------
    private static int[][] distilleryTransitable =
          {{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1},
           { 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 0, 0, 0, 0, 0, 0, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3},
           { 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3}};

    private static int[][] distilleryBounds =
        {{ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 0, 4, 4},
         { 5, 6, 0, 0, 6, 0, 0, 6, 0, 0, 0, 0, 0, 0, 7},
         { 8, 9, 9, 9, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0,10},
         { 0, 0, 0, 0, 0, 0, 5,11, 0, 0,12,13, 0, 0,14},
         { 0, 0, 0, 0, 0, 0, 5,15, 0, 0,16,17, 0, 0, 7},
         { 0, 0, 0, 0, 0, 0, 5,15, 0, 0,16,17, 0, 0,10},
         { 0, 0, 0, 0, 0, 0, 5,18, 0, 0,19,20, 0, 0,14},
         {21,22,22,22,22,22, 0, 0, 0, 0, 0, 0, 0, 0, 7},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
         { 8,23, 9,23, 9,23, 9,23, 9,23, 9, 9, 0, 9,24}};
    //Outer Distillery----------------------------------------------------------
    private static int[][] outerDistilleryTransitable =
        {{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1},
         { 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5},
         { 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4},
         { 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3, 4, 5, 3},
         { 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6},
         { 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7},
         { 8, 8, 8, 8, 8, 9, 8, 8, 8, 8, 8, 8, 8, 9, 8},
         { 8, 9, 8, 8, 8, 8, 8, 8, 8, 9, 8, 8, 8, 8, 8},
         { 8, 8, 8, 8, 8, 9, 8, 8, 8, 8, 8, 8, 8, 8, 9},
         { 8, 8, 8, 9, 8, 8, 8, 8, 8, 8, 8, 9, 8, 8, 8}};

    private static int[][] outerDistilleryBounds =
        {{10,10,10,10,10,10,10,10,10,10,10,10, 0,10,10},
         { 0, 0, 0,11, 0, 0,11, 0, 0,11, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0,12, 0, 0,12, 0, 0,12, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0,13, 0, 0, 0,13, 0, 0, 0,13, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}};
    //Outsides------------------------------------------------------------------
    private static int[][] outsidesTransitable =
        {{ 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 5},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 5, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 5},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 5, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 5},
         { 1, 2, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 4, 1}};

    private static int[][] outsidesBounds =
        {{ 0, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 8, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 7, 0, 0, 0, 0, 0, 0, 0, 0, 7, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 0, 0, 0, 0, 0, 9, 0, 0, 0, 0, 0, 8, 0},
         { 0, 0, 0, 0, 0, 0, 0, 9, 0, 0, 0, 0, 0, 0, 0},
         { 0, 0, 7, 0, 0, 0, 0,10, 0, 0, 0, 0, 7, 0, 0}};
    //Wolves data---------------------------------------------------------------
    private static int[][] wolves1Transitable =
          {{ 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
          { 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
          { 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
          { 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
          { 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0},
          { 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0}};

    private static int[][] wolves1Bounds =
          {{ 2, 3, 0, 0, 4, 5, 5, 5, 5, 5, 5, 6, 0, 7, 8},
          { 9, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7,10},
          { 9, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7,10},
          { 9, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7,10},
          { 2, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 7,11},
          { 9, 3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 5},
          {12,13, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,14,15,15,15},
          {15,15,15,15,15,16, 0, 0, 0, 0, 0, 7, 8,17,17}};

    private static int[][] wolves2Transitable =
          {{ 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 20},
          { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 0},
          { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 0},
          { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 0},
          { 0, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 3, 20},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 0},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}};

    private static int[][] wolves2Bounds =
          {{18,19, 5, 5, 5, 5, 5, 5, 6, 0, 0, 0, 0, 0, 0},
          {21,22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,23},
          {21,22, 0, 0, 0, 0, 0,14,24, 0, 0, 0, 0, 0,23},
          {21,22, 0,14,15,24, 0, 7,22, 0, 0, 0, 0, 0,23},
          {25,22, 0, 7,26,22, 0, 7,22, 0, 0, 0, 0, 0, 0},
          { 5, 6, 0, 4, 5, 6, 0, 7,22, 0, 0, 0, 0, 0,23},
          { 0, 0, 0, 0, 0, 0, 0, 4, 6, 0, 0, 0, 0,13,12},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          {15,15,15,15,24, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          {17,17,17,18,22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}};

    private static int[][] wolves3Transitable =
          {{ 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 0,27,27, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}};

    private static int[][] wolves3Bounds =
          {{28,29,28,29,30,22, 0, 0, 0, 0, 0, 7,11,31,31},
          { 5, 5, 5, 5, 5, 6, 0, 0, 0, 0, 0, 4, 5, 5, 5},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          {32, 0, 0,32,32,32,32,32,32,32,32,32,32,32,32},
          {33, 0, 0,33,33,34,33,33,33,33,34,33,33,34,34}};

    private static int[][] wolves4Transitable =
          {{ 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,27,27, 0}};

    private static int[][] wolves4Bounds =
          {{31,31,31,25,22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 5, 5, 5, 5, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
          {32,32,32,32,32,32,32,32,32,32,32,32, 0, 0,32},
          {33,34,33,33,33,34,33,33,33,34,33,33, 0, 0,33}};
    //CCI data------------------------------------------------------------------
    private static int[][] transitableCCIReceiverTiles =
          {{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 19},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 19},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 19},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}};
    private static int[][] boundsCCIReceiverTiles =
          {{ 3, 4, 4,17,17,17,17,17,17,17,17,17, 4, 18, 0},
           { 7, 0, 0,20,21,21,20,20,20,22,22,22, 0, 18, 0},
           { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18, 0},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           {14,15,15,15, 0,15,15,15,15,15, 0,15,15,15,16}};
    private static int[][] transitableCCIComputersTiles =
          {{ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1},
           { 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 1},
           { 1, 2, 1, 2, 1, 2, 1, 2, 1, 1, 1, 1, 1, 0, 1},
           { 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1},
           { 1, 2, 1, 2, 1, 2, 1, 2, 1, 1, 1, 1, 1, 1, 1},
           { 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 0, 1},
           { 1, 2, 1, 2, 1, 2, 1, 2, 1, 1, 1, 1, 1, 0, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1},
           { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1}};
    private static int[][] boundsCCIComputersTiles =
          {{ 3, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 5, 6},
           { 7, 8, 9, 8, 9, 8, 9, 8, 0, 0, 0, 0, 0, 5,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5,10},
           { 7, 8, 9, 8, 9,11, 9, 8, 0, 0, 0, 0, 0, 0, 0},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 8, 9, 8, 9, 8, 9, 8, 0, 0, 0, 0, 0,12,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,13,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           { 7, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,10},
           {14,15,15,15,15,15,15,15,15,15,15,15,15,15,16}};
    //--------------------------------------------------------------------------
    

    /**
     * Bridges the new map-type object to be built with TiledLayer using an existing tile set Image.
     * @param tiles Image containing the tiles to be drawn in the map.
     */
    public Map(int mapType, boolean boundaries, GameAdmin gameAdmin) throws IOException {
        super(HORIZONTAL_TILES, VERTICAL_TILES, Map.getMapTiles(mapType), TILE_SIZE, TILE_SIZE);
        this.mapType = mapType;
        this.createMap(boundaries);
        this.gameAdmin = gameAdmin;
    }

    //Creates the transitable and bounds map according to the parameter boundaries
    private void createMap(boolean boundaries) {
        switch (this.mapType) {
            case Map.FISHBOWL:
                if (boundaries) {
                    this.buildMap(Map.fishbowlBounds);
                } else {
                    this.buildMap(Map.fishbowlTransitable);
                }
                break;
            case Map.OUTER_FISHBOWL:
                if (boundaries) {
                    this.buildMap(Map.outerFishBowlBounds);
                } else {
                    this.buildMap(Map.outerFishbowlTransitable);
                }
                break;
            case Map.DISTILLERY:
                if (boundaries) {
                    this.buildMap(Map.distilleryBounds);
                } else {
                    this.buildMap(Map.distilleryTransitable);
                }
                break;
            case Map.WOLVES_UPPER_LEFT:
                if (boundaries) {
                    this.buildMap(Map.wolves1Bounds);
                } else {
                    this.buildMap(Map.wolves1Transitable);
                }
                break;
            case Map.WOLVES_UPPER_RIGHT:
                if (boundaries) {
                    this.buildMap(Map.wolves2Bounds);
                } else {
                    this.buildMap(Map.wolves2Transitable);
                }
                break;
            case Map.WOLVES_LOWER_LEFT:
                if (boundaries) {
                    this.buildMap(Map.wolves3Bounds);
                } else {
                    this.buildMap(Map.wolves3Transitable);
                }
                break;
            case Map.WOLVES_LOWER_RIGHT:
                if (boundaries) {
                    this.buildMap(Map.wolves4Bounds);
                } else {
                    this.buildMap(Map.wolves4Transitable);
                }
                break;
            case Map.CCI_COMPUTERS:
                if (boundaries) {
                    this.buildMap(Map.boundsCCIComputersTiles);
                } else {
                    this.buildMap(Map.transitableCCIComputersTiles);
                }
                break;
            case Map.CCI_RECEIVER:
                if (boundaries) {
                    this.buildMap(Map.boundsCCIReceiverTiles);
                } else {
                    this.buildMap(Map.transitableCCIReceiverTiles);
                }
                break;
            case Map.OUTER_DISTILLERY:
                if (boundaries) {
                    this.buildMap(Map.outerDistilleryBounds);
                } else {
                    this.buildMap(Map.outerDistilleryTransitable);
                }
                break;
            case Map.OUTSIDES:
                if (boundaries) {
                    this.buildMap(Map.outsidesBounds);
                } else {
                    this.buildMap(Map.outsidesTransitable);
                }
                break;
            default:
                System.out.println("Error in map type");
        }
    }

    /**
     * Requests the containing LayerManager to paint the current tiled map on screen.
     * @param g Graphics-type reference to be used to paint.
     */
    public void draw(Graphics g) {
        super.paint(g);
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkFishBowlBounds(int xPosition, int yPosition) {
        if ((xPosition >= Map.TILE_SIZE) && (xPosition <= Map.TILE_SIZE * 2)) {
            if (yPosition + Map.TILE_SIZE >= Map.MAP_HEIGHT) {
                gameAdmin.setPlayerPosition(FISHBOWL, Map.OUTER_FISHBOWL);
                gameAdmin.setCurrentScene(Map.OUTER_FISHBOWL);
            } else if (yPosition <= Map.TILE_SIZE) {
                gameAdmin.setPlayerPosition(FISHBOWL, Map.WOLVES_LOWER_LEFT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_LEFT);
            }
        } else if ((yPosition + (Map.TILE_SIZE * 2) >= Map.MAP_HEIGHT) && (yPosition <= Map.MAP_HEIGHT - Map.TILE_SIZE)) {
            if (xPosition + Map.TILE_SIZE >= Map.MAP_WIDTH) {
                gameAdmin.setPlayerPosition(FISHBOWL, Map.DISTILLERY);
                gameAdmin.setCurrentScene(Map.DISTILLERY);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkDistilleryBounds(int xPosition, int yPosition){
        if ( (Map.TILE_SIZE*12) <= xPosition  && xPosition <= (Map.MAP_WIDTH-Map.TILE_SIZE*2)) {
            if ( yPosition <= Map.TILE_SIZE*2 ) {
                gameAdmin.setPlayerPosition(DISTILLERY, Map.WOLVES_LOWER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_RIGHT);
            } else if ((yPosition + Map.TILE_SIZE) >= Map.MAP_HEIGHT) {
                gameAdmin.setPlayerPosition(DISTILLERY, Map.OUTER_DISTILLERY);
                gameAdmin.setCurrentScene(Map.OUTER_DISTILLERY);
            }
        } else if (xPosition <= 0) {
            if (yPosition + (Map.TILE_SIZE * 2)>= Map.MAP_HEIGHT && yPosition <= Map.MAP_HEIGHT-TILE_SIZE) {
                gameAdmin.setPlayerPosition(DISTILLERY, Map.FISHBOWL);
                gameAdmin.setCurrentScene(Map.FISHBOWL);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkOuterFishBowlBounds(int xPosition, int yPosition){
        if ( ( Map.TILE_SIZE <= xPosition ) && ( xPosition <= Map.TILE_SIZE*2 ) ) {
            if ( yPosition <= Map.TILE_SIZE ) {
                gameAdmin.setPlayerPosition(OUTER_FISHBOWL, Map.FISHBOWL);
                gameAdmin.setCurrentScene(Map.FISHBOWL);
            }
        } else if ( xPosition >= (Map.MAP_WIDTH-Map.TILE_SIZE) ) {
            if ( Map.TILE_SIZE <= yPosition ) {
                gameAdmin.setPlayerPosition(OUTER_FISHBOWL, OUTER_DISTILLERY);
                gameAdmin.setCurrentScene(OUTER_DISTILLERY);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkWolves1Bounds(int xPosition, int yPosition){
        if ( ( Map.TILE_SIZE*2 <= xPosition ) && ( xPosition <= Map.TILE_SIZE*4) ){
            if ( yPosition <= Map.TILE_SIZE ) {
                //Going to white tower
            }
        } else if ( ( ( Map.TILE_SIZE*12) <= xPosition ) && ( xPosition <= ( Map.TILE_SIZE*14 ) ) ) {
            if ( yPosition <= Map.TILE_SIZE ) {
                //Going to white tower
            }
        } else if ( (Map.TILE_SIZE*6) <= xPosition && xPosition <= (Map.TILE_SIZE*12) ) {
            if ( (Map.MAP_HEIGHT-Map.TILE_SIZE) <= yPosition ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_LEFT, Map.WOLVES_LOWER_LEFT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_LEFT);
            }
        } else if ( (Map.MAP_WIDTH-Map.TILE_SIZE) <= xPosition ){
            if ( (Map.TILE_SIZE*6) <= yPosition && yPosition <= (Map.MAP_HEIGHT-Map.TILE_SIZE*2)) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_LEFT, Map.WOLVES_UPPER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_RIGHT);
            }
        } else if ( Map.TILE_SIZE <= xPosition ) {
            if ( ( (Map.TILE_SIZE*7) <= yPosition ) && ( yPosition <= (Map.MAP_HEIGHT-Map.TILE_SIZE) ) ) {
                //Going to altar of wisdom
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkWolves2Bounds(int xPosition, int yPosition){
        if ( Map.TILE_SIZE >= xPosition ){
            if ( (Map.TILE_SIZE*6) <= yPosition && yPosition <= (Map.MAP_HEIGHT-Map.TILE_SIZE*2) ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_RIGHT, Map.WOLVES_UPPER_LEFT);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_LEFT);
            }
        } else if ( (Map.MAP_WIDTH-Map.TILE_SIZE) <= xPosition ) {
            if ( 0 <= yPosition && yPosition <= Map.TILE_SIZE) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_RIGHT, Map.CCI_RECEIVER);
                gameAdmin.setCurrentScene(Map.CCI_RECEIVER);
            } else if ( (Map.TILE_SIZE*4) <= yPosition && yPosition <= (Map.TILE_SIZE*5) ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_RIGHT, Map.CCI_RECEIVER_2);
                gameAdmin.setCurrentScene(Map.CCI_RECEIVER);
            }
        } else if ( Map.TILE_SIZE*5 <= xPosition ) {
            if ( (Map.MAP_HEIGHT-Map.TILE_SIZE) <= yPosition ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_UPPER_RIGHT, Map.WOLVES_LOWER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_RIGHT);
            }
        } else if ( (Map.TILE_SIZE*9) <= xPosition && xPosition <= (Map.MAP_WIDTH-Map.TILE_SIZE*2)) {
            if ( Map.TILE_SIZE <= yPosition ) {
                //Going to white tower
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkWolves3Bounds(int xPosition, int yPosition){
        if ( ( Map.TILE_SIZE <= xPosition ) && ( xPosition <= Map.TILE_SIZE*3) ){
            if ( (yPosition + Map.TILE_SIZE) >= Map.MAP_HEIGHT ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_LEFT, Map.FISHBOWL);
                gameAdmin.setCurrentScene(Map.FISHBOWL);
            }
        } else if ( ( ( Map.TILE_SIZE*6) <= xPosition ) && ( xPosition <= ( Map.TILE_SIZE*11 ) ) ) {
            if ( yPosition <= Map.TILE_SIZE ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_LEFT, Map.WOLVES_UPPER_LEFT);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_LEFT);
            }
        } else if ( (Map.MAP_WIDTH - Map.TILE_SIZE) <= xPosition ) {
            if ( ( Map.TILE_SIZE*2 <= yPosition ) && ( yPosition <= Map.MAP_HEIGHT-( Map.TILE_SIZE*2 ) ) ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_LEFT, Map.WOLVES_LOWER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_RIGHT);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkWolves4Bounds(int xPosition, int yPosition){
        if ( (Map.TILE_SIZE*5) <= xPosition ){
            if ( Map.TILE_SIZE >= yPosition ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_RIGHT, Map.WOLVES_UPPER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_RIGHT);
            }
        } else if ( Map.TILE_SIZE >= xPosition ) {
            if ( (Map.TILE_SIZE*2) <= yPosition && yPosition <= (Map.MAP_HEIGHT-Map.TILE_SIZE)) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_RIGHT, Map.WOLVES_LOWER_LEFT);
                gameAdmin.setCurrentScene(Map.WOLVES_LOWER_LEFT);
            }
        } else if ( (Map.TILE_SIZE*12) <= xPosition && xPosition <= (Map.MAP_WIDTH-Map.TILE_SIZE) ) {
            if ( (yPosition + Map.TILE_SIZE) >= Map.MAP_HEIGHT ) {
                gameAdmin.setPlayerPosition(Map.WOLVES_LOWER_RIGHT, Map.DISTILLERY);
                gameAdmin.setCurrentScene(Map.DISTILLERY);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkCCIReceiverBounds(int xPosition, int yPosition){
        if ( (Map.TILE_SIZE*4) <= xPosition && xPosition <= (Map.TILE_SIZE*5)) {
            if ( (Map.MAP_HEIGHT-Map.TILE_SIZE) <= yPosition ) {
                gameAdmin.setPlayerPosition(Map.CCI_RECEIVER, Map.WOLVES_UPPER_RIGHT);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_RIGHT);
            }
        } else if ( (Map.TILE_SIZE*10) <= xPosition && xPosition <= (Map.TILE_SIZE*11) ) {
            if ( (Map.MAP_HEIGHT-Map.TILE_SIZE) <= yPosition ) {
                gameAdmin.setPlayerPosition(Map.CCI_RECEIVER, Map.WOLVES_UPPER_RIGHT_2);
                gameAdmin.setCurrentScene(Map.WOLVES_UPPER_RIGHT);
            }
        } else if ( xPosition <= Map.TILE_SIZE ) {
            if ( (Map.TILE_SIZE*2) <= yPosition && yPosition <= (Map.TILE_SIZE*3) ) {
                gameAdmin.setPlayerPosition(Map.CCI_RECEIVER, Map.CCI_COMPUTERS);
                gameAdmin.setCurrentScene(Map.CCI_COMPUTERS);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkCCIComputersBounds(int xPosition, int yPosition){
        if ( (Map.MAP_WIDTH-Map.TILE_SIZE) <= xPosition ) {
            if ( (Map.TILE_SIZE*3) <= yPosition && yPosition <= (Map.TILE_SIZE*4) ) {
                gameAdmin.setPlayerPosition(Map.CCI_COMPUTERS, Map.CCI_RECEIVER);
                gameAdmin.setCurrentScene(Map.CCI_RECEIVER);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkOuterDistilleryBounds(int xPosition, int yPosition){
        if ( xPosition <= Map.TILE_SIZE ) {
            if ( yPosition >= Map.TILE_SIZE ) {
                gameAdmin.setPlayerPosition(OUTER_DISTILLERY, OUTER_FISHBOWL);
                gameAdmin.setCurrentScene(OUTER_FISHBOWL);
            }
        } else if ( (Map.TILE_SIZE*12) <= xPosition && xPosition <= (Map.MAP_WIDTH-(Map.TILE_SIZE*2)) ) {
            if ( yPosition <= Map.TILE_SIZE ) {
                gameAdmin.setPlayerPosition(OUTER_DISTILLERY, DISTILLERY);
                gameAdmin.setCurrentScene(DISTILLERY);
            }
        } else if ( 0 <= xPosition && xPosition <= Map.MAP_WIDTH ) {
            if ( (yPosition + Map.TILE_SIZE) >= Map.MAP_HEIGHT ) {
                gameAdmin.setPlayerPosition(OUTER_DISTILLERY, OUTSIDES);
                gameAdmin.setCurrentScene(OUTSIDES);
            }
        }
    }

    /**
     * Checks if player is in a door and change map if needed
     * @param xPosition player position at the horizontal axis
     * @param yPosition player position at the vertical axis
     */
    public void checkOutsidesBounds(int xPosition, int yPosition){
       if ( yPosition <= Map.TILE_SIZE ) {
           gameAdmin.setPlayerPosition(OUTSIDES, OUTER_DISTILLERY);
           gameAdmin.setCurrentScene(OUTER_DISTILLERY);
       }
    }

    /**
     * Tiled map builder method. Uses the information matrix of an inherited subclass and sets the cells of the new map with the information
     * found.
     * @param tilesMatrix Bidimensional integer matrix specified within inherited subclasses, containing the necessary information to create the
     * Tiled map.
     */
    public void buildMap(int[][] tilesMatrix){
        int i,j;
        for (i = 0; i < tilesMatrix.length; i++) {
            for (j = 0; j < tilesMatrix[0].length; j++) {
                this.setCell(j, i, tilesMatrix[i][j]);
            }
        }
    }

    /**
     * Selects the tiles according to the map code
     * @param mapCode integer code representing the map
     * @return the tiles of the map
     * @throws IOException if Image does not exist
     */
    public static Image getMapTiles(int mapCode) throws IOException {
        switch (mapCode) {
            case Map.FISHBOWL:
                return Image.createImage("/Images/Maps/Fishbowl.png");
            case Map.DISTILLERY:
                return Image.createImage("/Images/Maps/Distillery.png");
            case Map.OUTER_FISHBOWL:
                return Image.createImage("/Images/Maps/OuterFishbowl.png");
            case Map.OUTER_DISTILLERY:
                return Image.createImage("/Images/Maps/OuterDistillery.png");
            case Map.CCI_COMPUTERS :
                return Image.createImage("/Images/Maps/CCI.png");
            case Map.CCI_RECEIVER :
                return Image.createImage("/Images/Maps/CCI.png");
            case WOLVES_LOWER_RIGHT:
                return Image.createImage("/Images/Maps/Wolves.png");
            case WOLVES_UPPER_LEFT:
                return Image.createImage("/Images/Maps/Wolves.png");
            case WOLVES_UPPER_RIGHT:
                return Image.createImage("/Images/Maps/Wolves.png");
            case WOLVES_LOWER_LEFT:
                return Image.createImage("/Images/Maps/Wolves.png");
            case Map.OUTSIDES:
                return Image.createImage("/Images/Maps/Outsides.png");
            default:
                System.out.println("Bad image code at getMapTiles");
                return Image.createImage("Bad image code");
        }
    }

}